home *** CD-ROM | disk | FTP | other *** search
- # Source Generated with Decompyle++
- # File: in.pyc (Python 2.5)
-
- import os
- import config
- import eventloop
- from templatehelper import quoteattr, escape, attrPattern, rawAttrPattern, resourcePattern, generateId
- from templateoptimize import HTMLChangeOptimizer
- from xhtmltools import urlencode
- from template_compiler import checkU
- from itertools import chain
- import logging
- import util
- import re
- HTMLPattern = re.compile('^.*<body.*?>(.*)</body\\s*>', re.S)
- if os.environ.has_key('DEMOCRACY_RECOMPILE_TEMPLATES'):
- import template_compiler
- import resources
- template_compiler.setResourcePath(resources.path(''))
-
-
- def fillTemplate(filename, domHandler, platform, eventCookie, bodyTagExtra = '', top = True, onlyBody = False, *args, **kargs):
- if os.environ.has_key('DEMOCRACY_RECOMPILE_TEMPLATES'):
- (tcc, handle) = template_compiler.compileTemplate(filename)
- exec tcc.getOutput() in locals()
- return fillTemplate(domHandler, platform, eventCookie, bodyTagExtra, *args, **kargs)
- else:
- filename = filename.replace('/', '.').replace('\\', '.').replace('-', '_')
- components = filename.split('.')
- mod = __import__('compiled_templates.%s' % filename)
- for comp in components:
- mod = getattr(mod, comp)
-
- return mod.fillTemplate(domHandler, platform, eventCookie, bodyTagExtra, *args, **kargs)
-
-
- def fillStaticTemplate(filename, platform = '', eventCookie = 'noCookie', bodyTagExtra = '', onlyBody = False, *args, **kargs):
- (tch, handle) = fillTemplate(filename, None, platform, eventCookie, bodyTagExtra, *args, **kargs)
- handle.unlinkTemplate()
- rv = tch.read()
- if onlyBody:
- rv = HTMLPattern.match(rv).group(1)
-
- return rv
-
-
- def queueDOMChange(func, name):
- """Queue function that does a bunch of DOM updates to a display.
-
- What happens is a little weird, we queue a call in the main gui thread
- loop, then we queue a second call in the backend loop. If that call does
- any DOM updates like changeItems, addItemBefore, etc., those will almost
- certainly be queued back into the main loop.
-
- The rational for this is that if the main loop is busy it's better to wait
- for it to be idle if we have a bunch of changes. That way we can group
- things together and have them happen all at once. This may seem like it
- adds a bunch of latency, but this doesn't seem to be the case,
- addUrgentCall() happens quickly and if we are waiting on the gui thread,
- that means we're doing some other kind of gui update.
- """
- import frontend
-
- try:
- (None, frontend.inMainThread)((lambda : eventloop.addUrgentCall(func, name)))
- except:
- eventloop.addIdle(func, name)
-
-
-
- def queueSelectDisplay(frame, display, area):
- '''Queue a call to MainFrame.selectDisplay using queueDOMChange. This is
- useful if you want it to happen after template DOM updates (see
- selection.py for an example).
- '''
- if area in toSelect:
- toSelect[area].unlink()
-
- toSelect[area] = display
- (None, queueDOMChange)((lambda : doSelectDisplay(frame, area)), 'Select display')
-
- toSelect = { }
-
- def doSelectDisplay(frame, area):
- if area in toSelect:
- frame.selectDisplay(toSelect.pop(area), area)
-
-
-
- class TrackedView:
-
- def __init__(self, anchorId, anchorType, view, templateFunc, parent, name):
- self.anchorId = anchorId
- self.anchorType = anchorType
- self.view = view
- self.templateFunc = templateFunc
- self.parent = parent
- self.htmlChanger = parent.htmlChanger
- self.name = name
- self.toChange = { }
- self.toRemove = []
- self.toAdd = []
- self.addBefore = None
- self.idle_queued = False
-
-
- def tid(self, obj):
- return 'objid-%s-%d' % (id(self), id(obj))
-
-
- def initialFillIn(self):
- self.view.confirmDBThread()
- self.toChange = { }
- self.toRemove = []
- self.toAdd = []
- self.addBefore = None
- self.addObjects(self.view)
- self.view.addChangeCallback(self.onChange)
- self.view.addAddCallback(self.onAdd)
- self.view.addResortCallback(self.onResort)
- self.view.addRemoveCallback(self.onRemove)
-
-
- def onUnlink(self):
- self.view.removeChangeCallback(self.onChange)
- self.view.removeAddCallback(self.onAdd)
- self.view.removeResortCallback(self.onResort)
- self.view.removeRemoveCallback(self.onRemove)
-
-
- def initialXML(self, item):
- xml = self.currentXML(item)
- self.htmlChanger.setInitialHTML(self.tid(item), xml)
- return xml
-
-
- def currentXML(self, item):
- xml = self.templateFunc(item, self.name, self.view, self.tid(item)).read()
- return xml
-
-
- def callback(self):
- self.toChange = { }
- self.toRemove = []
- self.toAdd = []
- self.addBefore = None
- self.idle_queued = False
-
-
- def addCallback(self):
- if not self.idle_queued:
- queueDOMChange(self.callback, 'TrackedView DOM Change (%s)' % self.name)
- self.idle_queued = True
-
-
-
- def onResort(self):
- self.toChange = { }
- self.toRemove = []
- self.toAdd = []
- self.addBefore = None
- self.addObjects(self.view)
-
-
- def onChange(self, obj, id):
- if obj in self.toAdd:
- return None
-
- self.toChange[id] = obj
- self.addCallback()
-
-
- def onAdd(self, obj, id):
- if len(self.toChange) > 0 or len(self.toRemove) > 0:
- self.callback()
-
- if self.parent.domHandler:
- next = self.view.getNextID(id)
- if next is not None:
- nextTid = self.tid(self.view.getObjectByID(next))
- else:
- nextTid = None
- for i in range(len(self.toAdd)):
- if self.tid(self.toAdd[i]) == nextTid:
- self.toAdd.insert(i, obj)
- self.addCallback()
- return None
- continue
-
- if len(self.toAdd) > 0 and nextTid == self.addBefore:
- self.toAdd.append(obj)
- self.addCallback()
- else:
- self.callback()
- self.toAdd.append(obj)
- self.addBefore = nextTid
- self.addCallback()
-
-
-
- def addObjects(self, objects):
- '''Insert the XML for a list of objects into the DOM tree.'''
- if len(objects) == 0:
- return None
-
- xmls = [ self.initialXML(x) for x in objects ]
- for xmls_part in util.partition(xmls, 100):
- self.addXML(''.join(xmls_part))
-
-
-
- def addXML(self, xml):
- if self.addBefore:
- self.parent.domHandler.addItemBefore(xml, self.addBefore)
- elif self.anchorType in ('parentNode', 'containerDiv'):
- self.parent.domHandler.addItemAtEnd(xml, self.anchorId)
-
- if self.anchorType == 'nextSibling':
- self.parent.domHandler.addItemBefore(xml, self.anchorId)
-
-
-
- def onRemove(self, obj, id):
- if obj in self.toAdd:
- self.toAdd.remove(obj)
- return None
-
- if len(self.toAdd) > 0:
- self.callback()
-
- if id in self.toChange:
- del self.toChange[id]
-
- self.toRemove.append(obj)
- self.addCallback()
-
-
-
- class UpdateRegionBase:
- '''Base class for UpdateRegion and ConfigUpdateRegion. Subclasses must
- define renderXML, which returns a string representing the up-to-date XML
- for this region. Also, hookupCallbacks() which hooks up any callbacks
- needed. Subclasses can use onChange() as the handler for any callbacks.
- '''
-
- def __init__(self, anchorId, anchorType, templateFunc, parent):
- self.anchorId = anchorId
- self.anchorType = anchorType
- self.templateFunc = templateFunc
- self.parent = parent
- self.htmlChanger = self.parent.htmlChanger
- self.tid = generateId()
- self.idle_queued = False
-
-
- def initialFillIn(self):
- if self.parent.domHandler:
- self.parent.domHandler.addItemBefore(self.initialXML(), self.anchorId)
-
- self.hookupCallbacks()
-
-
- def initialXML(self):
- xml = self.renderXML()
- self.htmlChanger.setInitialHTML(self.tid, xml)
- return xml
-
-
- def onChange(self, *args, **kwargs):
- if not self.idle_queued:
- queueDOMChange(self.doChange, 'UpdateRegion DOM Change (%s)' % self.name)
- self.idle_queued = True
-
-
-
- def doChange(self):
- xml = self.renderXML()
- changes = self.parent.htmlChanger.calcChanges(self.tid, xml)
- if changes and self.parent.domHandler:
- self.parent.domHandler.changeItems(changes)
-
- self.idle_queued = False
-
-
-
- class UpdateRegion(UpdateRegionBase):
-
- def __init__(self, anchorId, anchorType, view, templateFunc, parent, name):
- UpdateRegionBase.__init__(self, anchorId, anchorType, templateFunc, parent)
- self.view = view
- self.name = name
-
-
- def renderXML(self):
- return self.templateFunc(self.name, self.view, self.tid).read()
-
-
- def hookupCallbacks(self):
- self.view.addChangeCallback(self.onChange)
- self.view.addAddCallback(self.onChange)
- self.view.addRemoveCallback(self.onChange)
- self.view.addResortCallback(self.onChange)
- self.view.addViewChangeCallback(self.onChange)
-
-
- def onUnlink(self):
- self.view.removeChangeCallback(self.onChange)
- self.view.removeAddCallback(self.onChange)
- self.view.removeRemoveCallback(self.onChange)
- self.view.removeResortCallback(self.onChange)
- self.view.removeViewChangeCallback(self.onChange)
-
-
-
- class ConfigUpdateRegion(UpdateRegionBase):
-
- def __init__(self, anchorId, anchorType, templateFunc, parent):
- UpdateRegionBase.__init__(self, anchorId, anchorType, templateFunc, parent)
- self.name = 'ConfigUpdateRegion'
-
-
- def hookupCallbacks(self):
- config.addChangeCallback(self.onChange)
-
-
- def onUnlink(self):
- config.removeChangeCallback(self.onChange)
-
-
- def renderXML(self):
- return self.templateFunc(self.tid).read()
-
-
-
- class Handle:
-
- def __init__(self, domHandler, templateVars, document = None, onUnlink = (lambda : None)):
- self.domHandler = domHandler
- self.templateVars = templateVars
- self.document = document
- self.trackedHides = { }
- self.trackedViews = []
- self.updateRegions = []
- self.subHandles = []
- self.triggerActionURLsOnLoad = []
- self.triggerActionURLsOnUnload = []
- self.onUnlink = onUnlink
- self.htmlChanger = HTMLChangeOptimizer()
- self.filled = False
-
-
- def addTriggerActionURLOnLoad(self, url):
- self.triggerActionURLsOnLoad.append(str(url))
-
-
- def addTriggerActionURLOnUnload(self, url):
- self.triggerActionURLsOnUnload.append(str(url))
-
-
- def getTriggerActionURLsOnLoad(self):
- return self.triggerActionURLsOnLoad
-
-
- def getTriggerActionURLsOnUnload(self):
- return self.triggerActionURLsOnUnload
-
-
- def getTemplateVariable(self, name):
- return self.templateVars[name]
-
-
- def addUpdateHideOnView(self, id, view, hideFunc, previous):
-
- checkFunc = lambda *args: self._checkHide(id)
- self.trackedHides[id] = (view, hideFunc, checkFunc, previous)
- if self.filled:
- self.addHideChecks(view, checkFunc)
-
-
-
- def _checkHide(self, id):
- (view, hideFunc, checkFunc, previous) = self.trackedHides[id]
- if hideFunc() != previous:
- self.trackedHides[id] = (view, hideFunc, checkFunc, not previous)
- if previous:
- self.domHandler.showItem(id)
- else:
- self.domHandler.hideItem(id)
-
-
-
- def addView(self, anchorId, anchorType, view, templateFunc, name):
- tv = TrackedView(anchorId, anchorType, view, templateFunc, self, name)
- self.trackedViews.append(tv)
-
-
- def addUpdate(self, anchorId, anchorType, view, templateFunc, name):
- ur = UpdateRegion(anchorId, anchorType, view, templateFunc, self, name)
- self.updateRegions.append(ur)
-
-
- def forceUpdate(self):
- for ur in self.updateRegions:
- ur.onChange()
-
- for h in self.subHandles:
- h.forceUpdate()
-
-
-
- def addConfigUpdate(self, anchorId, anchorType, templateFunc):
- ur = ConfigUpdateRegion(anchorId, anchorType, templateFunc, self)
- self.updateRegions.append(ur)
-
-
- def unlinkTemplate(self, top = True):
- self.domHandler = None
-
- try:
- self.document.unlink()
- except:
- pass
-
- self.document = None
- for o in chain(self.trackedViews, self.updateRegions):
- o.onUnlink()
-
- self.trackedViews = []
- self.updateRegions = []
- if self.filled:
- for id in self.trackedHides.keys():
- (view, hideFunc, checkFunc, previous) = self.trackedHides[id]
- self.removeHideChecks(view, checkFunc)
-
-
- self.trackedHides = { }
- for handle in self.subHandles:
- handle.unlinkTemplate()
-
- self.subHandles = []
- self.templateVars.clear()
- self.onUnlink()
-
-
- def initialFillIn(self):
- for ur in self.updateRegions:
- ur.initialFillIn()
-
- for tv in self.trackedViews:
- tv.initialFillIn()
-
- for handle in self.subHandles:
- handle.initialFillIn()
-
- for id in self.trackedHides.keys():
- (view, hideFunc, checkFunc, previous) = self.trackedHides[id]
- self.addHideChecks(view, checkFunc)
-
- self.filled = True
-
-
- def addHideChecks(self, view, checkFunc):
- logging.debug('Add hide checks: function %s on view %s', checkFunc, view)
- view.addChangeCallback(checkFunc)
- view.addAddCallback(checkFunc)
- view.addRemoveCallback(checkFunc)
- view.addResortCallback(checkFunc)
- view.addViewChangeCallback(checkFunc)
- checkFunc()
-
-
- def removeHideChecks(self, view, checkFunc):
- logging.debug('Remove hide checks: function %s on view %s', checkFunc, view)
- view.removeChangeCallback(checkFunc)
- view.removeAddCallback(checkFunc)
- view.removeRemoveCallback(checkFunc)
- view.removeResortCallback(checkFunc)
- view.removeViewChangeCallback(checkFunc)
-
-
- def addSubHandle(self, handle):
- self.subHandles.append(handle)
-
-
-
- def returnFalse(x):
- return False
-
-
- def returnTrue(x):
- return True
-
-
- def identityFunc(x):
- return x
-
-
- def nullSort(x, y):
- return 0
-
-
- def quoteAndFillAttr(value, localVars):
- checkU(value)
- return ''.join(('"', quoteattr(fillAttr(value, localVars)), '"'))
-
-
- def fillAttr(_value, _localVars):
- checkU(_value)
- match = attrPattern.match(_value)
- if match:
- result = eval(match.group(2), globals(), _localVars)
- return ''.join((match.group(1), urlencode(result), match.group(3)))
- else:
- match = rawAttrPattern.match(_value)
- if match:
- result = eval(match.group(2), globals(), _localVars)
- return ''.join((match.group(1), result, match.group(3)))
- else:
- match = resourcePattern.match(_value)
- if match:
- return resources.url(match.group(1))
- else:
- return _value
-
- import compiled_templates
-